<template>
  <div class="szLogin sz-login__index">
    <!-- tabs -->
    <section class="tabs">
      <div
        class="tabs_item"
        :class="activeTab === item && 'active'"
        v-for="item in tabs"
        :key="item"
        @click="handleChangeTab(item)"
      >
        <div class="name">{{ TABS[item].text }}</div>
      </div>
    </section>

    <!-- form -->
    <section class="form">
      <el-form
        ref="loginFormRef"
        :model="loginForm"
        :rules="loginRules"
        @validate="handleValidate"
      >
        <template v-if="activeTab === LOGIN_ACTION.ACCOUNT">
          <el-form-item prop="account">
            <el-input
              v-model="loginForm.account"
              placeholder="请输入用户名"
            ></el-input>
          </el-form-item>
          <el-form-item prop="password">
            <el-input
              type="password"
              v-model="loginForm.password"
              placeholder="请输入密码"
              show-password
            ></el-input>
          </el-form-item>
        </template>
        <template v-if="activeTab === LOGIN_ACTION.PHONE">
          <el-form-item prop="phone" class="phoneInput">
            <el-input
              name="phone"
              v-model="loginForm.phone"
              placeholder="请输入手机号"
            >
              <template slot="prefix">+86</template>
            </el-input>
          </el-form-item>
          <el-form-item prop="captcha" class="captchaGroup">
            <el-input
              name="captcha"
              v-model="loginForm.captcha"
              placeholder="请输入验证码"
            >
            </el-input>
            <el-button
              class="captchaButton"
              :class="hasSendSms && 'countdown'"
              :disabled="hasSendSms"
              @click="handleGetImgCaptcha"
              >{{
                hasSendSms ? `重新获取(${countdown})` : "获取验证码"
              }}</el-button
            >
          </el-form-item>
        </template>
      </el-form>
      <!-- errTip -->
      <div class="err-tip">{{ errTip }}</div>
      <el-button class="confirmButton" type="primary" @click="handleSubmit"
        >登录</el-button
      >
    </section>
  </div>
</template>

<script>
import {
  sendLoginSms,
  checkLoginCaptcha,
  loginByPhone,
  loginByAccount
} from "@/apis/login";
import { checkPhoneNumber } from "@/utils/validator";
import { LOGIN_ACTION } from "@/utils/enum";
import cookie from "@/utils/cookie";
let countdownId = null;
const TABS = {
  [LOGIN_ACTION.ACCOUNT]: { text: "密码登录" },
  [LOGIN_ACTION.PHONE]: { text: "手机登录" },
  [LOGIN_ACTION.WEIXIN]: { text: "微信登录" }
};
export default {
  name: "loginPage",
  props: {
    tabs: {
      type: Array,
      default: () => []
    },
    platform: {
      type: String,
      default: ""
    },
    imgCaptchaInfo: {
      type: Object,
      default: () => {}
    },
    setCookie: {
      type: Boolean,
      default: true
    }
  },
  data() {
    return {
      TABS,
      LOGIN_ACTION,
      activeTab: this.tabs[0],
      loginForm: {
        account: "",
        password: "",
        phone: "",
        captcha: ""
      },
      loginRules: {
        account: [
          { required: true, message: "请输入用户名", trigger: "change" }
        ],
        password: [
          { required: true, message: "请输入密码", trigger: "change" }
        ],
        phone: [
          { required: true, validator: checkPhoneNumber, trigger: "blur" }
        ],
        captcha: [{ required: true, message: "请输入验证码", trigger: "blur" }]
      },
      hasSendSms: false, // 一分钟之内只能发送一次验证码
      countdown: 60,
      errTip: ""
    };
  },
  watch: {
    imgCaptchaInfo(newVal, oldVal) {
      if (newVal && newVal.captcha && newVal.captcha !== oldVal.captcha) {
        this.handleCheckImgCaptcha(newVal);
      }
    }
  },
  methods: {
    handleChangeTab(tab) {
      this.activeTab = tab;
      this.$refs["loginFormRef"].clearValidate();
      this.$refs["loginFormRef"].resetFields();
      this.errTip = "";
    },
    handleValidate() {
      this.errTip = "";
    },
    handleGetImgCaptcha() {
      this.$refs["loginFormRef"].validateField("phone", (error) => {
        if (!error) {
          this.$emit("openDialog");
        }
      });
    },
    // 设置AUTHORIZATION
    setAuthorizationCookie(data) {
      if (!this.setCookie) return;
      cookie.set(`AUTHORIZATION_${this.platform.toUpperCase()}`, data);
    },
    // 设置USERINFO
    setUserInfoCookie(data) {
      if (!this.setCookie) return;
      cookie.set(
        `USERINFO_${this.platform.toUpperCase()}`,
        JSON.stringify(data)
      );
    },
    async handleCheckImgCaptcha({ captcha, verifyKey }) {
      try {
        const params = {
          captcha,
          cellphone: this.loginForm.phone,
          regionCode: "86",
          verKey: verifyKey
        };
        const res = await sendLoginSms(params, {
          customApi: this.$attrs.customApi
        });
        if (res.status === 1) {
          this.$message.success("验证码已发送");
          this.$emit("closeDialog");

          // 禁用获取验证码按钮
          this.hasSendSms = true;
          countdownId = setInterval(() => {
            if (this.countdown > 0) {
              this.countdown -= 1;
            } else {
              clearInterval(countdownId);
              this.hasSendSms = false;
              this.countdown = 60;
            }
          }, 1000);
        } else {
          this.$emit("closeDialog");
          this.$message({ type: 'error', message: res.message });
        }
      } catch (err) {
        console.error(err);
      }
    },
    // 手机号登录
    async submitPhoneLogin() {
      try {
        const res = await loginByPhone(
          {
            cellphone: this.loginForm.phone,
            code: this.loginForm.captcha,
            redirect: 0
          },
          { customApi: this.$attrs.customApi }
        );
        if (res) {
          this.setAuthorizationCookie(res.AUTHORIZATION);
          this.setUserInfoCookie(res.USERINFO);
          this.$emit("success", LOGIN_ACTION.PHONE, res, this.loginForm);
        }
      } catch (err) {
        this.$emit("failed", LOGIN_ACTION.PHONE, err, this.loginForm);
        console.error(err);
      }
    },
    // 校验手机验证码
    async checkPhoneLogin() {
      try {
        const res = await checkLoginCaptcha(
          {
            cellphone: this.loginForm.phone,
            code: this.loginForm.captcha
          },
          { customApi: this.$attrs.customApi }
        );
        if (res.status === 1) {
          this.submitPhoneLogin();
        } else {
          this.errTip = res.message;
        }
      } catch (err) {
        console.error(err);
      }
    },
    // 账号登录
    async submitLoginByAccount() {
      try {
        const res = await loginByAccount(
          {
            loginName: this.loginForm.account,
            password: this.loginForm.password
          },
          {
            source: this.platform,
            customApi: this.$attrs.customApi
          }
        );
        if (res) {
          // 展示账号登录的错误信息
          this.setAuthorizationCookie(res.authorization);
          this.setUserInfoCookie(res);
          this.$emit("success", LOGIN_ACTION.ACCOUNT, res, this.loginForm);
        }
      } catch (err) {
        this.$emit("failed", LOGIN_ACTION.ACCOUNT, err, this.loginForm);
        this.errTip = err.message;
        console.error(err);
      }
    },
    handleSubmit() {
      this.$refs["loginFormRef"].validate((valid) => {
        if (valid) {
          if (this.activeTab === "phone") {
            this.checkPhoneLogin();
          } else {
            this.submitLoginByAccount();
          }
        }
      });
    }
  },
  beforeDestroy() {
    if (countdownId) {
      clearInterval(countdownId);
    }
  }
};
</script>

<style lang="scss">
@import url("/styles/login.scss");
.sz-login__index {
  .tabs {
    display: flex;
    justify-content: space-around;

    &_item {
      cursor: pointer;
      .name {
        color: #606266;
        font-size: 20px;
      }
    }

    .active {
      position: relative;
      &::after {
        content: "";
        height: 5px;
        width: 100%;
        background: linear-gradient(90deg, #1677ff, rgba(22, 119, 255, 0) 100%);
        display: block;
        position: absolute;
        bottom: 0;
        left: 0;
      }
      .name {
        color: #303133;
        font-weight: 600;
      }
    }
  }

  .err-tip {
    color: #f56c6c;
    font-size: 12px;
    line-height: 1;
    margin-top: -16px;
  }

  .form {
    margin: 36px 0;
  }

  .confirmButton {
    width: calc(100% - 80px);
    position: absolute;
    bottom: 70px;
    height: 44px;
  }
}
</style>
